package pod

import (
	"context"
	"fmt"
	log "github.com/sirupsen/logrus"
	corev1 "k8s.io/api/core/v1"
	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
	"k8s.io/client-go/kubernetes/scheme"
	"k8s.io/client-go/tools/remotecommand"
	"os"
	"twwch/k8s-admin/apis"
	"twwch/k8s-admin/application/base"
	"twwch/k8s-admin/models/pod"
)

type PodService struct {
	base.BaseService
}

var svc = &PodService{}

func GetService() *PodService {
	svc.Logger = log.WithField("service", "pod")
	return svc
}

func (svc *PodService) List(ctx context.Context, req *pod.ListReq) (*pod.ListResp, error) {
	listOptions := metav1.ListOptions{
		LabelSelector: fmt.Sprintf("app=%v", req.DeployName),
	}
	pods, err := apis.CoreV1().Pods(req.Namespace).List(ctx, listOptions)
	if err != nil {
		svc.Logger.Error(ctx, err)
		return nil, err
	}
	resp := &pod.ListResp{
		Pods: pods,
	}
	return resp, nil
}

func (svc *PodService) Exec(ctx context.Context, req *pod.ExecReq) (*pod.ExecResp, error) {
	reqData := apis.CoreV1().RESTClient().Post().
		Resource("pods").
		Name(req.Name).
		Namespace(req.Namespace).
		SubResource("exec").
		VersionedParams(&corev1.PodExecOptions{
			Command: req.Command,
			Stdin:   true,
			Stdout:  true,
			Stderr:  true,
			TTY:     false,
		}, scheme.ParameterCodec)

	exec, err := remotecommand.NewSPDYExecutor(apis.Config(), "POST", reqData.URL())
	if err != nil {
		return nil, err
	}

	screen := &pod.ExecResp{
		Reader: os.Stdin, Writer: os.Stdout,
	}

	if err = exec.Stream(remotecommand.StreamOptions{
		Stdin:  screen,
		Stdout: screen,
		Stderr: screen,
		Tty:    false,
	}); err != nil {
		return nil, err
	}
	return screen, nil
}
